#pragma once
#include "DataType.h"
#include "BaseSample.h"

#define DESTROY_3D_DATA(pcData) { \
	if (NULL != pcData) { \
		pcData->x_num = 0; \
		pcData->y_num = 0; \
		IA_FREE(pcData->Px); \
		IA_FREE(pcData->Py); \
		IA_FREE(pcData->Pz); \
		IA_FREE(pcData->intensity); \
		pcData = NULL; \
}}

/**
 * @brief 3D data defination
 *				From algo team, do not modify this structure
 */
typedef struct
{
	int x_num;
	int y_num;
	float* Px;
	float* Py;
	float* Pz;
	float* intensity;
}IA_PC_D5X;

/**
 * @brief 3D data context from intensity data
 */
typedef struct
{
	float XResolution;
	float YResolution;
	float ZResolution;
	float XOffset;
	float YOffset;
	float ZOffset;
	float DataType;
}IA_3D_CONTEXT;

/**
 * @file CImage3D.h
 *
 * @brief Wrapper class of structure PC_D5X
 *u
 * @author cygia.com
 * Contact: lance.liao@cygia.com
 *
 */
class CImage3D :
	public CDataType, public CBaseSample
{
public:
	CBaseSample* CreateInstance();

public:
	CImage3D();
	CImage3D(IA_PC_D5X* _data3D);
	CImage3D(int cols, int rows);
	~CImage3D();
	CImage3D* Copy();
	IA_PC_D5X* CopyToPCData();

public:
	int Create(int cols, int rows);
	void Destroy();

	int SaveTo(const char* pPath);
	int LoadFrom(const char* pPath);

	int SaveAsTIF(const char* pPath);
	int ReadFromTIF(const char* pPath);

	int ExportAsCSV(const char* pPath);
	int SaveToXYZ(const char* pPath);

	int GetDataContext(IA_3D_CONTEXT& dataContext);

	int Mirror(int isX, int isY);

public: 
	int GetW() { return _data3D.x_num; }
	int GetH() { return _data3D.y_num; }

	float* GetPX() { return _data3D.Px; }
	float* GetPY() { return _data3D.Py; }
	float* GetPZ() { return _data3D.Pz; }
	float* GetPI() { return _data3D.intensity; }
	IA_PC_D5X* GetPC() { return &_data3D; }

public:
	static void DestroyPCData(IA_PC_D5X*& pcData);

private:
	void Default();
	int ParseCorrd(std::string line, float* pEncoder, int encoderNum);

	IA_PC_D5X _data3D;

};

